package org.liveboardgames.common;

import java.util.Map;

import org.hibernate.collection.PersistentMap;
import org.liveboardgames.common.util.ExternalMap;

import flex.messaging.io.BeanProxy;
import flex.messaging.io.PropertyProxyRegistry;

/**
 * This class makes BlazeDS uses the real entity classname instead of the
 * hibernate proxy classname, this is needed so the entity can be used as a
 * value object (RemoteClass) in flex, else flex will give a type coercion error
 * because the classname mismatches. See the following thread on the BlazeDS
 * forum for more information:
 * http://www.adobe.com/cfusion/webforums/forum/messageview
 * .cfm?forumid=72&catid=667&threadid=1335887&enterthread=y
 * 
 * @author Steven De Kock
 */
public class HibernatePropertyProxy extends BeanProxy {

  private static final long serialVersionUID = 1612371743382649972L;

  /**
   * Registers this class with BlazeDS to handle HibernateProxy instances
   */
  public HibernatePropertyProxy() {
    super();
    PropertyProxyRegistry.getRegistry().register(Map.class, this);
  }

  /**
   * Get actual name instead of cglib class name with $$enhancerByCglib in it.
   */
  protected String getClassName(Object o) {
    if (o instanceof Map) {
      return ExternalMap.class.getName();
    }
    else {
      return super.getClassName(o);
    }
  }

  @Override
  public Object getInstanceToSerialize(Object instance) {
    // TODO Auto-generated method stub
    Object instanceToSerialize = null;
    if (instance instanceof Map) {
      instanceToSerialize = new ExternalMap();
      PersistentMap map = (PersistentMap)instance;
      for (Object key : map.keySet()) {
        ((Map)instanceToSerialize).put(key, map.get(key));
      }
    }
    else {
      instanceToSerialize = super.getInstanceToSerialize(instance);
    }
    return instanceToSerialize;
  }
}